package com.erp.user.service.impl;

import com.baomidou.mybatisplus.core.conditions.Wrapper;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.erp.common.enums.DeleteEnum;
import com.erp.common.exception.BaseBizException;
import com.erp.common.response.ListVo;
import com.erp.common.utils.BeanUtils;
import com.erp.user.entity.Permit;
import com.erp.user.entity.RolePermit;
import com.erp.user.mapper.PermitMapper;
import com.erp.user.request.*;
import com.erp.user.response.PermitDetailInfoResp;
import com.erp.user.response.PermitInfoResp;
import com.erp.user.response.PermitSearchInfoResp;
import com.erp.user.service.PermitService;
import com.erp.user.service.RolePermitService;
import org.apache.commons.collections4.CollectionUtils;
import org.apache.commons.compress.utils.Lists;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.List;
import java.util.Objects;
import java.util.Set;


/**
 * @author shensong
 * @program machining_system.v1.0.0
 * @description 权限 服务实现类
 * @date 2022/12/21 10:54:42
 */
@Service("permitService")
public class PermitServiceImpl extends ServiceImpl<PermitMapper, Permit> implements PermitService {

    @Autowired
    private RolePermitService rolePermitService;

    @Override
    public ListVo<List<PermitInfoResp>> index(PermitPageReq request) {
        LambdaQueryWrapper<Permit> queryWrapper = Wrappers.lambdaQuery();
        if (Objects.nonNull(request)) {
            queryWrapper.eq(Objects.nonNull(request.getId()),Permit::getId, request.getId());
            queryWrapper.eq(Objects.nonNull(request.getPid()),Permit::getPid, request.getPid());
            queryWrapper.eq(StringUtils.isNotBlank(request.getName()),Permit::getName, request.getName());
            queryWrapper.eq(Objects.nonNull(request.getType()),Permit::getType, request.getType());
            queryWrapper.eq(StringUtils.isNotBlank(request.getPermissionValue()),Permit::getPermissionValue, request.getPermissionValue());
            queryWrapper.eq(StringUtils.isNotBlank(request.getPath()),Permit::getPath, request.getPath());
            queryWrapper.eq(StringUtils.isNotBlank(request.getComponent()),Permit::getComponent, request.getComponent());
            queryWrapper.eq(StringUtils.isNotBlank(request.getIcon()),Permit::getIcon, request.getIcon());
            queryWrapper.eq(Objects.nonNull(request.getStatus()),Permit::getStatus, request.getStatus());
            queryWrapper.eq(StringUtils.isNotBlank(request.getSort()),Permit::getSort, request.getSort());
            queryWrapper.eq(StringUtils.isNotBlank(request.getRemark()),Permit::getRemark, request.getRemark());
            queryWrapper.eq(Objects.nonNull(request.getRevision()),Permit::getRevision, request.getRevision());
            queryWrapper.eq(Objects.nonNull(request.getGmtCreate()),Permit::getGmtCreate, request.getGmtCreate());
            queryWrapper.eq(Objects.nonNull(request.getGmtModified()),Permit::getGmtModified, request.getGmtModified());
        }
        queryWrapper.eq(Permit::getIsDeleted, DeleteEnum.NO.getCode());
        queryWrapper.orderByDesc(Permit::getId);
        IPage<Permit> data = this.queryPage(request.getPageNum(), request.getPageSize(), queryWrapper);
        if (Objects.nonNull(data) && CollectionUtils.isNotEmpty(data.getRecords())) {
            List<PermitInfoResp> permitListResponse = BeanUtils.copyObjects(data.getRecords(), PermitInfoResp.class);
            return new ListVo<>(permitListResponse, data.getTotal(), data.getSize(), data.getCurrent());
        }

        return new ListVo<>();
    }

    @Override
    public Boolean store(PermitAddReq request) {
        Set<Long> roleIds = request.getRoleIds();
        Permit entity = BeanUtils.copyProperties(request, Permit.class);
        Boolean status = this.save(entity);

        if(status){
            return updateRolePermit(entity.getId(), roleIds);
        }
        return status;
    }

    @Override
    public Boolean update(PermitUpdateReq request) {
        Permit permit = this.getById(request.getId());
        if(Objects.isNull(permit)){
            throw new BaseBizException("没有数据");
        }
        Set<Long> roleIds = request.getRoleIds();
        Permit entity = BeanUtils.copyProperties(request, Permit.class);
        Boolean status = this.updateById(entity);

        if(status){
            return updateRolePermit(entity.getId(), roleIds);
        }
        return status;
    }

    @Override
    public Boolean destroy(PermitDeleteReq request) {
        Permit permit = this.getById(request.getId());
        if(Objects.isNull(permit)){
            throw new BaseBizException("没有数据");
        }
        LambdaUpdateWrapper<Permit> updateWrapper = Wrappers.lambdaUpdate();
        updateWrapper.set(Permit::getIsDeleted, DeleteEnum.YES.getCode()).eq(Permit::getId, request.getId());
        Boolean status = this.update(updateWrapper);

        if(status){
            return updateRolePermit(request.getId(), null);
        }
        return status;
    }

    @Override
    public PermitInfoResp show(PermitInfoReq request) {
        LambdaQueryWrapper<Permit> queryWrapper = Wrappers.lambdaQuery();
        queryWrapper.eq(Permit::getId, request.getId());
        queryWrapper.eq(Permit::getIsDeleted, DeleteEnum.NO.getCode());
        Permit entity = this.getOne(queryWrapper);
        return Objects.nonNull(entity) ? BeanUtils.copyProperties(entity, PermitInfoResp.class) : null;
    }

    @Override
    public Boolean approve(PermitApproveReq request) {
        Permit entity = BeanUtils.copyProperties(request, Permit.class);
        return this.updateById(entity);
    }

    @Override
    public Boolean enabled(PermitStatusReq request) {
        Permit entity = BeanUtils.copyProperties(request, Permit.class);
        return this.updateById(entity);
    }

    @Override
    public List<PermitInfoResp> option(PermitListReq request) {
        LambdaQueryWrapper<Permit> queryWrapper = Wrappers.lambdaQuery();
        if (Objects.nonNull(request)) {
            queryWrapper.eq(Objects.nonNull(request.getId()), Permit::getId, request.getId());
            queryWrapper.eq(Objects.nonNull(request.getPid()), Permit::getPid, request.getPid());
            queryWrapper.eq(StringUtils.isNotBlank(request.getName()), Permit::getName, request.getName());
            queryWrapper.eq(Objects.nonNull(request.getType()), Permit::getType, request.getType());
            queryWrapper.eq(StringUtils.isNotBlank(request.getPermissionValue()), Permit::getPermissionValue, request.getPermissionValue());
            queryWrapper.eq(StringUtils.isNotBlank(request.getPath()), Permit::getPath, request.getPath());
            queryWrapper.eq(StringUtils.isNotBlank(request.getComponent()), Permit::getComponent, request.getComponent());
            queryWrapper.eq(StringUtils.isNotBlank(request.getIcon()), Permit::getIcon, request.getIcon());
            queryWrapper.eq(Objects.nonNull(request.getStatus()), Permit::getStatus, request.getStatus());
            queryWrapper.eq(Objects.nonNull(request.getIsDeleted()), Permit::getIsDeleted, request.getIsDeleted());
            queryWrapper.eq(StringUtils.isNotBlank(request.getSort()), Permit::getSort, request.getSort());
            queryWrapper.eq(StringUtils.isNotBlank(request.getRemark()), Permit::getRemark, request.getRemark());
            queryWrapper.eq(Objects.nonNull(request.getRevision()), Permit::getRevision, request.getRevision());
            queryWrapper.eq(Objects.nonNull(request.getGmtCreate()), Permit::getGmtCreate, request.getGmtCreate());
            queryWrapper.eq(Objects.nonNull(request.getGmtModified()), Permit::getGmtModified, request.getGmtModified());
        }

        queryWrapper.orderByDesc(Permit::getId);
        List<Permit> data = this.list(queryWrapper);
        return CollectionUtils.isNotEmpty(data) ? BeanUtils.copyObjects(data, PermitInfoResp.class) : Lists.newArrayList();
    }

    @Override
    public List<PermitSearchInfoResp> search(PermitSearchReq request) {
        LambdaQueryWrapper<Permit> queryWrapper = Wrappers.lambdaQuery();
        if (Objects.nonNull(request)) {
                queryWrapper.eq(Objects.nonNull(request.getId()), Permit::getId, request.getId());
                queryWrapper.eq(Objects.nonNull(request.getPid()), Permit::getPid, request.getPid());
                queryWrapper.eq(StringUtils.isNotBlank(request.getName()), Permit::getName, request.getName());
                queryWrapper.eq(Objects.nonNull(request.getType()), Permit::getType, request.getType());
                queryWrapper.eq(StringUtils.isNotBlank(request.getPermissionValue()), Permit::getPermissionValue, request.getPermissionValue());
                queryWrapper.eq(StringUtils.isNotBlank(request.getPath()), Permit::getPath, request.getPath());
                queryWrapper.eq(StringUtils.isNotBlank(request.getComponent()), Permit::getComponent, request.getComponent());
                queryWrapper.eq(StringUtils.isNotBlank(request.getIcon()), Permit::getIcon, request.getIcon());
                queryWrapper.eq(Objects.nonNull(request.getStatus()), Permit::getStatus, request.getStatus());
                queryWrapper.eq(StringUtils.isNotBlank(request.getSort()), Permit::getSort, request.getSort());
                queryWrapper.eq(StringUtils.isNotBlank(request.getRemark()), Permit::getRemark, request.getRemark());
                queryWrapper.eq(Objects.nonNull(request.getRevision()), Permit::getRevision, request.getRevision());
                queryWrapper.eq(Objects.nonNull(request.getGmtCreate()), Permit::getGmtCreate, request.getGmtCreate());
                queryWrapper.eq(Objects.nonNull(request.getGmtModified()), Permit::getGmtModified, request.getGmtModified());
        }
        queryWrapper.eq(Permit::getIsDeleted, request.getIsDeleted());
        queryWrapper.orderByDesc(Permit::getId);
        List<Permit> data = this.list(queryWrapper);
        return CollectionUtils.isNotEmpty(data) ? BeanUtils.copyObjects(data, PermitSearchInfoResp.class) : Lists.newArrayList();
    }

    @Override
    public PermitDetailInfoResp detail(PermitInfoReq request) {
        return BeanUtils.copyProperties(this.show(request), PermitDetailInfoResp.class);
    }

    private IPage<Permit> queryPage(Long pageNum, Long pageSize, Wrapper<Permit> queryWrapper) {
        IPage<Permit> selectPage = new Page<>();
        selectPage.setCurrent(pageNum);
        selectPage.setSize(pageSize);

        IPage<Permit> page = this.baseMapper.selectPage(selectPage, queryWrapper);
        return page;
    }

    private Boolean updateRolePermit(Long permitId, Set<Long> roleIds){
        LambdaQueryWrapper<RolePermit> queryWrapper = Wrappers.lambdaQuery();
        queryWrapper.eq(RolePermit::getPermitId, permitId);
        Boolean s = rolePermitService.remove(queryWrapper);

        if(CollectionUtils.isNotEmpty(roleIds)){
            List<RolePermit> rolePermitList = Lists.newArrayList();
            roleIds.forEach(roleId->{
                RolePermit rolePermitEntity = new RolePermit();
                rolePermitEntity.setRoleId(roleId);
                rolePermitEntity.setPermitId(permitId);
                rolePermitList.add(rolePermitEntity);
            });

            return rolePermitService.saveBatch(rolePermitList);
        }

        return s;
    }

}
